<template>
  <div class="note-box" v-loading="loading">
    <div class="note-box-list">
      <div id="list-header">
        <h2 class="clip">Notes | {{ getRealName(userInfo.userName) }}</h2>
      </div>
      <!--菜单列表-->
      <div class="list-menu">
        <el-scrollbar
          ref="menuScrollRef"
          style="flex: 1"
          @wheel.native.prevent="onHandleScroll"
        >
          <div style="display: flex; flex-wrap: nowrap; width: auto">
            <el-tag
              style="font-size: 14px; margin-right: 10px; cursor: pointer"
              :class="activeMenuClass"
              v-for="(item, index) in menuList"
              :key="index"
              @click="handleMenu(item, index)"
              :effect="index === menuIndex ? 'dark' : 'plain'"
              aria-flowto=""
              >{{ item.configName }}</el-tag
            >
          </div>
        </el-scrollbar>
        <div
          style="
            width: 30px;
            display: flex;
            justify-content: flex-end;
            text-align: right;
            align-items: center;
          "
        >
          <el-popover placement="bottom-end" :width="200" trigger="click">
            <template #reference>
              <font-awesome-icon
                style="user-select: none; outline: 0; cursor: pointer"
                class="f18 gray1"
                :icon="['fas', 'bars']"
              />
            </template>
            <div
              style="
                max-height: 600px;
                overflow-y: auto;
                padding: 30px 10px;
                padding-top: 10px;
              "
            >
              <el-row class="menu-head">
                <el-col :span="20"><h3>菜单分组</h3></el-col>
                <el-col :span="4" style="text-align: right">
                  <font-awesome-icon
                    @click="handleMenuAdd"
                    class="f18 gray1"
                    :icon="['fa', 'plus']"
                  />
                </el-col>
              </el-row>

              <el-row
                class="sub-item"
                v-for="(item, index) in menuList"
                :key="index"
              >
                <el-col :span="20">{{ item.configName }}</el-col>
                <el-col
                  :span="4"
                  style="text-align: right; cursor: pointer; font-size: 16px"
                >
                  <el-button
                    type="text"
                    v-if="item.configId"
                    @click="handleMenuDelete(item)"
                    ><font-awesome-icon :icon="['fa', 'xmark']"
                  /></el-button>
                </el-col>
              </el-row>
            </div>
          </el-popover>
        </div>
      </div>
      <!-- render note list -->
      <div
        :class="{ container: true }"
        v-loading="noteLoading"
        v-infinite-scroll="loadingScroll"
        infinite-scroll-throttle-delay="200"
        infinite-scroll-distance="10"
        :infinite-scroll-disabled="noteLoading || queryForm.nomore"
        :infinite-scroll-immediate="false"
      >
        <ul class="list-group" v-if="filteredNotes.length > 0">
          <li
            v-for="(note, index) in filteredNotes"
            class="list-group-item"
            :class="{ active: activeNote === index }"
            @click="setActiveNote(index)"
            @mouseenter="handleEnter(index)"
            @mouseleave="handleLeave(index)"
          >
            <h4 class="list-group-item-heading">
              <font-awesome-icon
                :icon="note.configId === '2' ? 'table' : 'file-word'"
                :class="note.configId === '2' ? 'iconExcel' : 'iconWord'"
              ></font-awesome-icon>
              {{ note.title ? note.title.trim() : "New Note" }}
            </h4>
            <span class="list-group-item-date gray-title">
              {{ note.date }}
            </span>
            <div class="op-btns" v-show="note.show">
              <sub-menus
                :row="note"
                :get-list="getList"
                :configIndex="menuIndex"
                :menu-list="menuList"
              ></sub-menus>
            </div>
            <div class="op-btns" v-show="!note.show">
              <font-awesome-icon
                v-if="note.favoritesFlag"
                style="color: #fec432"
                :icon="['fas', 'star']"
              />
            </div>
          </li>
        </ul>
        <div
          v-else
          style="
            height: 500px;
            display: flex;
            align-items: center;
            justify-content: center;
            color: #999999;
            font-weight: 500;
            font-size: 23px;
          "
        >
          暂无笔记
        </div>
        <div class="tips" v-if="noteLoading">加载中...</div>
        <div class="tips" v-if="queryForm.nomore">-没有更多了-</div>
      </div>
      <add-note
        :get-list="getList"
        :configIndex="menuIndex"
        :menu-list="menuList"
        :setActiveNote="setActiveNote"
      ></add-note>
    </div>
    <div class="note-box-edit">
      <div style="" class="edit-head">
        <input
          class="no-border"
          v-model.trim="formInfo.title"
          placeholder="请在这里输入标题..."
          spellcheck="false"
          maxlength="50"
          @blur="toSave"
        />
        <div
          class="flex"
          style="
            width: 350px;
            margin-right: 20px;
            align-items: center;
            justify-content: space-between;
          "
        >
          <span class="f14 saveTip" v-if="saveLoading">
            <font-awesome-icon
              style="margin-right: 5px"
              :icon="['fa', 'spinner']"
            />
            正在保存</span
          >
          <span class="f14 saveTip flex" v-else>
            <font-awesome-icon
              style="margin-right: 5px; color: #67c23a"
              :icon="['fa', 'check']"
            />
            已保存</span
          >

          <el-button type="default" @click="toSave" style="margin-left: 10px">
            保存
          </el-button>
          <span
            class="f20 flex"
            style="align-items: center; justify-content: center"
          >
            <el-avatar
              style="margin-right: 15px; margin-left: 0px; cursor: pointer"
              @click="handlePersonSet"
              :size="40"
              :src="userInfo.avatar"
            />
            <font-awesome-icon
              :icon="['far', 'bell']"
              style="margin-right: 15px"
              @click="handleChat"
            />
            <el-switch
              active-color="#2c2c2c"
              inactive-color="#f2f2f2"
              :active-action-icon="Moon"
              :inactive-action-icon="Sunny"
              v-model="isDark"
            />
          </span>
        </div>
      </div>
      <div class="boder-line"></div>
      <amis-editor
        v-show="formInfo.configId === '1'"
        ref="editorRef"
        @blur="hanldeTextBlur"
      ></amis-editor>
      <univer-sheet
        v-show="formInfo.configId === '2'"
        id="sheet"
        ref="univerRef"
      ></univer-sheet>
      <div
        v-if="contentLoading"
        v-loading="contentLoading"
        style="width: 100%; height: 100%; position: absolute; top: 0"
      ></div>
    </div>
    <person-setting
      ref="personRef"
      :avatar="userInfo.avatar"
      @logout="handleLogout"
    ></person-setting>
    <!--添加菜单-->
    <menu-add
      v-model:value="menuFlag"
      @complete="handleMenuCompelte"
      :note-list="noteList"
      ref="menuRef"
    ></menu-add>
    <!--chat-->
    <chat-box ref="chartRef"></chat-box>
  </div>
</template>

<script lang="ts">
import {
  defineComponent,
  onBeforeMount,
  reactive,
  toRefs,
  ref,
  onMounted,
  getCurrentInstance,
  toRaw,
  nextTick,
} from "vue";
import { Sunny, Moon } from "@element-plus/icons-vue";
import { getNoteList, writeNote } from "@/api/home";
import { menuList, deleteMenu } from "@/api/menu";
import { getUser } from "@/api/user";
import menuAdd from "./src/menuAdd.vue";
import subMenus from "./src/subMenus.vue";
import addNote from "./src/addNote.vue";
import personSetting from "./src/personSetting.vue";
import AmisEditor from "@/components/AmisEditor/index.vue";
import dayjs from "dayjs";
import { ElMessage, ElMessageBox } from "element-plus";
import { useDark, useToggle } from "@vueuse/core";
import UniverSheet from "@/components/UniverSheet.vue";
import { getRealName } from "@/utils/common";
import { useRouter } from "vue-router";
import userStore from "@/store/user";

export default defineComponent({
  components: {
    menuAdd,
    AmisEditor,
    subMenus,
    personSetting,
    UniverSheet,
    addNote,
  },
  setup() {
    const state = reactive({
      showPersonSetting: false,
      activeMenuClass: "",
      loadingNoteClass: false,
      show: false,
      filteredNotes: [],
      noteTag: "所有笔记",
      formInfo: {
        userId: "",
        content: "",
        title: "",
        configId: "",
      },
      userName: "",
      activeNote: 0,
      showChild: false,
      loading: false,
      noteLoading: false,
      loginFlag: false,
      saveLoading: false,
      menuIndex: 0,
      menuFlag: false,
      noteList: [],
      userInfo: {},
      loginForm: {
        userName: "",
        passWord: "",
      },
      queryForm: {
        limit: 15,
        pageNo: 1,
        configId: null,
        favoritesFlag: null,
        index: 0,
        nomore: false,
      },
      menuList: [],
      timer: null,
      contentLoading: false,
    });

    const isDark = useDark({
      storageKey: "useDarkKEY",
      valueDark: "dark",
      valueLight: "light",
    });
    const toggleDark = useToggle(isDark);
    const router = useRouter();
    const { proxy } = getCurrentInstance() as any;
    const setShow = () => {};
    const setActiveNote = async (val: any) => {
      await nextTick();
      if (state.filteredNotes.length > 0) {
        state.activeNote = val;
        console.log(state.filteredNotes[val], "state.filteredNotes[val]");
        state.formInfo = JSON.parse(JSON.stringify(state.filteredNotes[val]));
        if (state.formInfo.configId === "2") {
          proxy.$refs.univerRef.init(JSON.parse(state.formInfo.content));
        } else {
          console.log(JSON.stringify(state.formInfo), "state.formInfo.content");
          proxy.$refs.editorRef.setContent(state.formInfo.content);
        }
      }
    };

    const store = userStore();

    const handleEnter = (val: any) => {
      state.filteredNotes[val].show = true;
    };

    const hanldeTextBlur = (val) => {
      state.formInfo.content = val;
      toSave();
    };

    const toSave = async () => {
      if (state.formInfo.configId === "2") {
        state.formInfo.content = JSON.stringify(
          proxy.$refs.univerRef.getData()
        );
      }

      if (state.saveLoading) {
        return false;
      }
      if (!state.formInfo.noteId) {
        ElMessage.error("暂无笔记");
        return false;
      }
      state.saveLoading = true;
      let res = await writeNote(toRaw(state.formInfo));
      if (res.status == 0) {
        state.filteredNotes[state.activeNote] = JSON.parse(
          JSON.stringify(state.formInfo)
        );
        // getList(state.menuList[state.menuIndex], state.menuIndex);
        state.saveLoading = false;
      } else {
        ElMessage.error(res.message);
      }
    };

    const handleLeave = (val: any) => {
      state.filteredNotes[val].show = false;
    };

    const getMenuList = async () => {
      let res = await menuList({});
      if (res.status == 0) {
        state.menuList = res.data;
        state.menuList.unshift({ configName: "收藏", favoritesFlag: true });
        state.menuList.unshift({ configName: "所有笔记" });
      }
    };

    const handleMenuDelete = async (row) => {
      ElMessageBox.confirm("确认要删除", {
        confirmButtonText: "是",
        cancelButtonText: "否",
        type: "warning",
      })
        .then(async () => {
          state.loading = true;
          let res = await deleteMenu({ configId: row.configId });
          state.loading = false;
          if (res.status == 0) {
            getMenuList();
            getList(state.menuList[0], 0);
          } else {
            ElMessage.error(res.message);
          }
        })
        .catch(() => {});
    };

    // 鼠标滚轮滚动
    const onHandleScroll = (e: any) => {
      console.log("开始滚动");
      proxy.$refs.menuScrollRef.setScrollLeft(
        proxy.$refs.menuScrollRef.wrapRef.scrollLeft + e.wheelDelta / 4
      );
    };

    const getList = (row, index) => {
      state.queryForm.pageNo = 1;
      state.queryForm.nomore = false;
      state.queryForm.index = index;
      //不传row代表刷新当前菜单
      if (row) {
        state.queryForm.configId = row.configId;
        state.queryForm.favoritesFlag = row.favoritesFlag;
      }
      getNotePageList();
    };

    const loadingScroll = () => {
      if (state.timer) {
        clearTimeout(state.timer);
      }
      state.timer = setTimeout(() => {
        console.log(state.queryForm.pageNo, "state.queryForm.pageNo");
        state.queryForm.pageNo++;
        getNotePageList();
      }, 150);
    };

    const getNotePageList = async () => {
      state.loadingNoteClass = true;
      setTimeout(() => {
        state.loadingNoteClass = false;
      }, 500);
      state.noteLoading = true;
      let res = await getNoteList(toRaw(state.queryForm));
      console.log("111");
      state.noteLoading = false;
      if (res.status == 0) {
        const result = res.data.resultData.map((x) => {
          return {
            noteId: x.noteId,
            title: x.title,
            content: x.content,
            date: x.createTime,
            favoritesFlag: x.favoritesFlag,
            show: false,
            configId: x.configId,
          };
        });
        if (state.queryForm.pageNo === 1) {
          state.filteredNotes = JSON.parse(JSON.stringify(result));
        } else {
          state.filteredNotes.push(...JSON.parse(JSON.stringify(result)));
        }
        if (
          result.length < state.queryForm.limit &&
          state.filteredNotes.length > 0
        ) {
          state.queryForm.nomore = true;
        }

        state.menuIndex = state.queryForm.index;
      }
    };

    /***
     * row=点击菜单信息
     * index=点击菜单索引
     */
    const handleMenu = (row, index) => {
      state.activeMenuClass = "shake";
      setTimeout(() => {
        state.activeMenuClass = "";
      }, 200);
      state.contentLoading = true;
      getList(row, index);
      setTimeout(() => {
        state.contentLoading = false;
        //设置选中该菜单第一条
        setActiveNote(0);
      }, 1000);
    };

    const handleMenuAdd = (index) => {
      state.menuFlag = true;
      proxy.$refs.menuRef.reset();
    };

    const loadData = () => {
      getMenuList();
      // 判断是否本地已有缓存
      getList(null, 0);
      setTimeout(() => {
        //设置选中该菜单第一条
        setActiveNote(0);
      }, 1000);
    };

    const getUserInfo = async () => {
      let res = await getUser();
      if (res.status == 0) {
        state.userInfo = res.data;
        store.userInfo = res.data;
        proxy.$refs.chartRef.openSocket(state.userInfo);
      } else {
        ElMessage.error(res.message);
      }
      state.activeNote = 0;
    };

    const handleMenuCompelte = () => {
      loadData();
    };

    const handlePersonSet = () => {
      proxy.$refs.personRef.open();
    };

    const handleLogout = () => {
      sessionStorage.removeItem("token");
      router.push({
        path: "/login",
      });
    };

    const handleChat = () => {
      proxy.$refs.chartRef.open();
    };

    // watch(store.socket,
    //   (newVal:any) =>{
    //     if(newVal.status){
    //       // 断开用户链接
    //     }else{
    //         // 恢复用户链接
    //     }
    //   }
    // );

    onMounted(() => {
      getUserInfo();
      loadData();
    });

    return {
      ...toRefs(state),
      onHandleScroll,
      setShow,
      setActiveNote,
      handleEnter,
      handleLeave,
      hanldeTextBlur,
      toSave,
      getList,
      handleMenuAdd,
      handleMenuDelete,
      handleMenuCompelte,
      handleMenu,
      isDark,
      toggleDark,
      Sunny,
      Moon,
      handlePersonSet,
      loadingScroll,
      getRealName,
      handleLogout,
      handleChat,
    };
  },
});
</script>

<style lang="less" scoped>
h4 {
  font-weight: 300 !important;
  line-height: 1.1;
  color: inherit;
}

.active,
.list-group-item:hover {
  cursor: pointer;
  z-index: 0;
  background-color: var(--note-bg-hover);
  border-color: var(--note-bg-hover);
}

.add-btn {
  position: absolute;
  right: 10px;
  bottom: 30px;
}

.op-btns {
  position: absolute;
  font-size: 15px;
  top: 5px;
  right: 10px;
  display: flex;
  flex-direction: row;
  justify-content: flex-end;
  width: 40px;
  color: #666666;
}

.content-editor {
  border: 0;
  overflow: auto;
  outline: 0;
  font-size: 14px;
  color: #333333;
  flex: 1;
  width: 100%;
}

.el-input__inner:focus {
  outline: 0;
  box-shadow: none;
}
.edit-head {
  .el-input__inner {
    border: none !important;
    box-shadow: none !important;
    font-size: 20px;
    color: #555555;
    height: 40px;
    line-height: 40px;
    border: none !important;
    box-shadow: none !important;
  }
}

.no-border {
  height: 40px;
  border: 0px;
  font-weight: 500;
  width: 100%;
  font-size: 22px;
}

.no-border:focus {
  border: 0px;
  outline: 0;
}

.boder-line {
  width: 100%;
  border-bottom: solid 1px var(--note-line1);
}

.saveTip {
  margin-right: 10px;
  color: #a9b2c2;
  font-size: 12px;
}

.clip {
  font-family: Arial, Helvetica, sans-serif !important;
  font-size: 26px !important;
  --vp-home-hero-name-color: transparent;
  --vp-home-hero-name-background: -webkit-linear-gradient(
    120deg,
    #4c84ff 30%,
    rgb(77, 20, 144)
  );
  --vp-home-hero-image-background-image: linear-gradient(
    -45deg,
    #4c84ff 50%,
    rgb(77, 20, 144) 50%
  );
  background: var(--vp-home-hero-name-background);
  -webkit-background-clip: text;
  -webkit-text-fill-color: var(--vp-home-hero-name-color);
  margin-bottom: 5px;
}
</style>
